package com.zlsy.thread.threadsafe;

import java.util.concurrent.TimeUnit;

/**
 * @author zhouliang
 * @date 2020/03/20
 * <p>
 * 在构造函数中还没完成初始化就this赋值。
 **/
public class ThisAssignmentAdvanceNotSafe {

    static Point point;

    public static void main(String[] args) throws InterruptedException {
        new PoinMaker().start();
        //休眠500毫秒，打印出poin为Point{x=1, y=0}
        TimeUnit.MILLISECONDS.sleep(500);
        // 休眠1500 毫秒，打印出Point{x=1, y=1}
//        TimeUnit.MILLISECONDS.sleep(1500);

        //解析：随着执行时间的不同这个对象的值不同，这个是线程不安全的。
        //因为休眠500毫秒的时候，只完成了x的初始化，point被this赋值了
        //休眠1500毫秒的时候 x、y都被赋值了。


        //一个线程去初始化一个类，这个类是另外一个类的成员变量
        //main方法调用这个类的这个成员变量会得到不同的结果，导致是由于this的提前赋值导致的。
        // 这种在够着函数中还没完成初始化就this赋值的方式是线程不安全的。

        System.out.println(point);
    }
}

class Point {

    private final int x, y;

    public Point(int x, int y) throws InterruptedException {
        this.x = x;
        ThisAssignmentAdvanceNotSafe.point = this;
        TimeUnit.SECONDS.sleep(1);
        this.y = y;
    }

    @Override
    public String toString() {
        return "Point{" +
                "x=" + x +
                ", y=" + y +
                '}';
    }
}


class PoinMaker extends Thread {

    @Override
    public void run() {
        try {
            //初始化变量
            new Point(1, 1);
        } catch (InterruptedException e) {
            e.printStackTrace();
        }
    }
}
